<?php
class GrupoUsuariosBSN extends GenericBSN {

	function __construct() {
		$this->dao = new GrupoUsuariosDAO();
	}

	public function consultar($vars) {
		$this->preencher($vars);

		// contexto
		$grpCtxDao = new Grp_x_ContextoDAO();
		$ctx = $grpCtxDao->consultarUsuarioLogado(1);
		$this->dao->limitarContexto(!$ctx[0]['acessoConsulta']);
		// fim contexto

		if (!isset($vars["valor"]) || $vars['valor'] == "" || isset($vars['subde'])) {
			$grupos = array();
			if (isset($vars['subde']) and !is_null($vars['subde'])) {
				$grupos = $this->dao->consultarFilhos($vars['subde'], $this->order . $this->limit);
			} else {
				$dao = new Usu_x_GrupoDAO();
				foreach($dao->consultarGrupos($_SESSION['usuario']['id']) as $grp) {
					$grupos = array_merge($grupos, $this->dao->consultarPK($grp['grupoid']));
				}
			}
				
			$this->Records = $grupos;
			$this->TotalRecordCount = isset($vars['subde']) ? $this->dao->contarFilhos($vars['subde']) : count($grupos);   
		} else {
			$this->Records = $this->dao->consultar($this->where, $this->params, $this->order . $this->limit);
			$this->TotalRecordCount = $this->dao->contarRegistros($this->where, $this->params);   
		}
		$this->Result  = "OK";
	}
	
	public function consultarNome($nome) {
		// contexto
		$grpCtxDao = new Grp_x_ContextoDAO();
		$ctx = $grpCtxDao->consultarUsuarioLogado(1);
		$this->dao->limitarContexto(!$ctx[0]['acessoConsulta']);
		// fim contexto
		
		$this->Records = $this->dao->consultarGrupo($nome);
		$this->Result = "OK";
		$this->TotalRecordCount = $this->dao->contarRegistros("where grupo = '$nome'");   
	}
	
	public function consultarUsuarios($vars) {
		$grupo = $vars['grupoid'];
		
		// contexto
		$grpCtxDao = new Grp_x_ContextoDAO();
		$ctx = $grpCtxDao->consultarUsuarioLogado(1);
		$this->dao->limitarContexto(!$ctx[0]['acessoConsulta']);
		// fim contexto
		
	    $dao = new Usu_x_GrupoDAO();
	    $dao->limitarContexto(!$ctx[0]['acessoConsulta']);
		$this->Records = $dao->consultarUsuarios($grupo);
		$this->Result = "OK";
	}
	
	public function consultarUsuariosDisponiveis($vars) {
		// contexto
		$grpCtxDao = new Grp_x_ContextoDAO();
		$ctx = $grpCtxDao->consultarUsuarioLogado(1);
		$this->dao->limitarContexto(!$ctx[0]['acessoConsulta']);
		// fim contexto
		
	    $dao = new Usu_x_GrupoDAO();
	    // todo: verificar contexto do usu_x_grupo
		$this->Records = $dao->consultarUsuariosDisponiveis($vars['grupoid'], $vars["usuario"]);
		$this->Result = "OK";
	}

	public function consultarArvore($vars) {
		// contexto
		$grpCtxDao = new Grp_x_ContextoDAO();
		$ctx = $grpCtxDao->consultarUsuarioLogado(1);
		$this->dao->limitarContexto(!$ctx[0]['acessoConsulta']);
		// fim contexto
		
		$grupos = array();
		if (isset($vars['grupoid']) and !is_null($vars['grupoid'])) {
			$grupos = array_merge($grupos, $this->dao->consultarPK($vars['grupoid']));
		} else {
			$dao = new Usu_x_GrupoDAO();
			foreach($dao->consultarGrupos($_SESSION['usuario']['id']) as $grp) {
				$grupos = array_merge($grupos, $this->dao->consultarPK($grp['grupoid']));
			}
		}
		
		foreach($grupos as $ind => $grupo) {
			$grupos[$ind]['subs'] = $this->dao->consultarArvore($grupo['id']);
		}
		
		$this->Records = $grupos;
		$this->Result = "OK";
	}
	
	public function consultarContexto($grupo) {
		$ctx = new ContextoDAO();
		$grpdao = new Grp_x_ContextoDAO();
		
		if ($grupo == "null") {
			$res = $ctx->consultar("", null, "order by id");
			foreach($res as $key => $contexto) {
				$res[$key]['grupoid'] = $grupo;
				$res[$key]['acessoConsulta'] = 0;
				$res[$key]['acessoAlteracao'] = 0;
			}
		} else if ($grupo == "self") {
			$res = $grpdao->consultarUsuarioLogado();
			foreach($res as $key => $contexto) {
				$res[$key]['grupoid'] = $grupo;
			}
		} else {
			$res = $grpdao->consultarGrupo($grupo);
		}
		return $res;
	}
	
	public function consultarContextos($vars) {
		$grupos = explode(',', $vars['grupos']);
		$res = array();
		
		foreach($grupos as $grupo) {
			$res = array_merge($res, $this->consultarContexto($grupo));
		}

		$this->Records = $res;
		$this->Result = "OK";
	}
	
	public function inserir($vars, $finalizarTransacao = true) {
		try {
			$registro['grupo'] = $vars['grupo'];
			$registro['subde'] = isset($vars['subde']) ? $vars['subde'] : "null";
			
			// contexto
			$grpCtxDao = new Grp_x_ContextoDAO();
			$ctx = $grpCtxDao->consultarUsuarioLogado(1);
			if (!$ctx[0]['acessoAlteracao']) {
				if (!$this->dao->estaNoContexto($registro['subde'])) {
					throw new Exception("Tentativa de criar um Perfil fora do contexto permitido.");
				}
			}
			// fim contexto

			$acsDao = new AcessoDAO();
			
			$this->Record  = $this->dao->inserir($registro, false);
			$grpCtxDao->inserir(null, false);
			$acsDao->inserir(null, $finalizarTransacao);
				
			$this->Result  = "OK";
		} catch (Exception $e) {
			$this->dao->rollback();
			$this->Result  = "ERROR";
			$this->Message = $e->getMessage();
		}
	}
	
	public function inserirCustom($vars) {
		try {
			if ((!isset($vars["grupo"])) || ($vars["grupo"] == "")) {
				$grupo['grupo'] = "Custom";
			} else {
				$grupo['grupo'] = $vars['grupo'];
			}
			
			if (!is_numeric($grupo['grupo'])) {
				$i = "";
				$this->consultarNome($grupo['grupo']);
				while ($this->TotalRecordCount > 0) {
					$this->consultarNome($grupo['grupo'] . ++$i);
				}
				
				$grupo['grupo'] .= $i;
				$grupo['subde'] = "null";
				
				// contexto
				$grpCtxDao = new Grp_x_ContextoDAO();
				$ctx = $grpCtxDao->consultarUsuarioLogado(1);
				if (!$ctx[0]['acessoAlteracao']) {
					throw new Exception("Tentativa de criar um Perfil fora do contexto permitido.");
				} 
				// fim contexto
				
				$this->inserir($grupo, false);
			} else {
				$aux = $this->dao->consultarPK($vars['grupo']);
				$this->Record = $aux[0];
			}
			
			if (isset($vars["usuarios"]) && ($vars["usuarios"] <> "")) {
				foreach(explode(",", $vars["usuarios"]) as $usuid) {
					$novo['usuario'] = $usuid;
					$novo['grupoid'] = $this->Record["id"];
					$aux = $this->Record;
					$this->inserirUsuario($novo, false);
					$this->Record = $aux;
				}
			}
			
			$dao = new AcessoDAO();
			unset($novo);
			if (isset($vars["recursos"]) && ($vars["recursos"] <> "")) {
				foreach(explode(",", $vars["recursos"]) as $recid) {
					$novo["grupo"] = $this->Record["id"];
					$novo["recurso"] = $recid;
					$novo["acesso"] = 1;
					$dao->alterar($novo, false);
				}
			}
			$this->dao->commit();
			
			$this->Message = "Permissões personalizadas salvas com sucesso. Nome do novo grupo: " . $this->Record['grupo'];
			$this->Result  = "OK";
		} catch (Exception $e) {
			$this->dao->rollback();
			$this->Result  = "ERROR";
			$this->Message = $e->getMessage();
		}
	}

	public function inserirUsuario($vars, $finalizarTransacao = true) {
		try {
			if (!is_numeric($vars['usuario'])) {
				$dao = new UsuarioDAO();
				$usu = $dao->ConsultarNome($vars['usuario']);
				if (isset($usu[0]['id'])) {
					$reg['usuario'] = $usu[0]['id'];
				} else {
					throw new Exception("Usuário <b>" . $vars['usuario'] . "</b> não encontrado!");
				}
			} else {
				$reg['usuario'] = $vars['usuario'];
			}
			$reg['grupo'] = $vars['grupoid'];
	
			$res['usuario'] = $vars['usuario'];
			$res['grupoid'] = $vars['grupoid'];
			$res['pk']		= $reg['usuario'] . "," . $vars['grupoid'];
			
			// contexto
			$grpCtxDao = new Grp_x_ContextoDAO();
			$ctx = $grpCtxDao->consultarUsuarioLogado(1);
			if (!$ctx[0]['acessoAlteracao']) {
				if (!$this->dao->estaNoContexto($res['grupoid'])) {
					throw new Exception("Tentativa de inserir um usuário em um Perfil fora do contexto permitido.");
				}
			} 
			// fim contexto
					
			$dao = new Usu_x_GrupoDAO();
			$dao->Inserir($reg, $finalizarTransacao);
			
			$this->Record  = $res;
			$this->Result  = "OK";
		} catch (Exception $e) {
			$this->Result  = "ERROR";
			$this->Message = $e->getMessage();
		}
	}

	public function excluirUsuario($registro) {
		try {
			$dao = new Usu_x_GrupoDAO(); 
			$pk = explode(",", $registro["pk"]);
			$reg['usuario'] = $pk[0];
			$reg['grupo'] = $pk[1];

			// contexto
			$grpCtxDao = new Grp_x_ContextoDAO();
			$ctx = $grpCtxDao->consultarUsuarioLogado(1);
			if (!$ctx[0]['acessoAlteracao']) {
				if (!$this->dao->estaNoContexto($reg['grupo'])) {
					throw new Exception("Tentativa de excluir um usuário de um Perfil fora do contexto permitido.");
				}
			} 
			// fim contexto
					
			$dao->excluir($reg, $finalizarTransacao);
			$this->Result  = "OK";
		} catch (Exception $e) {
			$this->dao->rollback();
			$this->Result  = "ERROR";
			$this->Message = $e->getMessage();
		}
	}
	
	public function alterar($vars) {
		try {
			$registro['grupo'] 	= $vars['grupo'];
			$registro['subde'] 	= isset($vars['subde']) ? $vars['subde'] : "null";
			$registro['id']	   	= $vars['id'];
				
			// contexto
			$grpCtxDao = new Grp_x_ContextoDAO();
			$ctx = $grpCtxDao->consultarUsuarioLogado(1);
			if (!$ctx[0]['acessoAlteracao']) {
				if (!$this->dao->estaNoContexto($registro['subde'])) {
					throw new Exception("Tentativa de alterar um Perfil fora do contexto permitido.");
				}
			} 
			// fim contexto
					
			$ctxs = $this->consultarContexto("self");
			foreach ($ctxs as $ctx) {
				if (($ctx['acessoConsulta'] < $vars['acessoConsulta_' . $ctx['id']]) 
				|| ($ctx['acessoAlteracao'] < $vars['acessoAlteracao_' . $ctx['id']])) {
					throw new Exception('Tentativa de conceder uma permissão de contexto que não possui.');
				}
			}
			
			if ($registro['subde'] <> "null") {
				$ctxs = $this->consultarContexto($registro['subde']);
				foreach ($ctxs as $ctx) {
					if (($ctx['acessoConsulta'] < $vars['acessoConsulta_' . $ctx['id']]) 
					|| ($ctx['acessoAlteracao'] < $vars['acessoAlteracao_' . $ctx['id']])) {
						throw new Exception('Tentativa de conceder uma permissão de contexto a um Perfil sem que o Perfil pai a tenha.');
					}
				}
			}
			
			foreach ($ctxs as $ctx) {
				$regctx['grupousuarios'] 	= $registro['id'];
				$regctx['contexto']			= $ctx['id'];
				$regctx['acessoConsulta']	= $vars['acessoConsulta_' . $ctx['id']];
				$regctx['acessoAlteracao'] 	= $vars['acessoAlteracao_' . $ctx['id']];
				
				$dao = new Grp_x_ContextoDAO();
				$dao->alterar($regctx, false);
			}
			
			$this->Record  = $this->dao->alterar($registro);
			$this->Result  = "OK";
		} catch (Exception $e) {
			$this->dao->rollback();
			$this->Result  = "ERROR";
			$this->Message = $e->getMessage();
		}
	}

	public function excluir($registro) {
		$id = $registro['id'];

		// contexto
		$grpCtxDao = new Grp_x_ContextoDAO();
		$ctx = $grpCtxDao->consultarUsuarioLogado(1);
		if (!$ctx[0]['acessoAlteracao']) {
			if (!$this->dao->estaNoContexto($id)) {
				throw new Exception("Tentativa de excluir um Perfil fora do contexto permitido.");
			}
		} 
		// fim contexto
		
		try {
			$dao = new AcessoDAO();
			$res = $dao->excluirGrupo($id, false);
			$dao = new Grp_x_ContextoDAO();
			$res = $dao->excluirGrupo($id, false);
			$dao = new Usu_x_GrupoDAO();
			$res = $dao->excluirGrupo($id, false);

			$this->dao->Excluir($id);
			$this->Result  = "OK";
		} catch (Exception $e) {
			$this->dao->rollback();
			$this->Result  = "ERROR";
			$this->Message = $e->getMessage();
		}
	}
}
?>